iT邦幫忙

2019 iT 邦幫忙鐵人賽

DAY 19
1
自我挑戰組

ROS自學筆記系列 第 19

Day 19 - 使用C++撰寫Client Node

  • 分享至 

  • xImage
  •  

寫完C++的server,接著就是client囉!
C++版本跟python版本最不同的地方應該在於python版的不用做node的初始化,但是C++版本的還是需要喔!
首先還是先創一個新的add_two_ints_client.cpp檔:

$ roscd beginner_tutorials/src
$ vim add_two_ints_client.cpp

程式碼如下:

   1 #include "ros/ros.h"
   2 #include "rospy_tutorials/AddTwoInts.h"
   3 #include <cstdlib>
   4 
   5 int main(int argc, char **argv)
   6 {
   7   ros::init(argc, argv, "add_two_ints_client");
   8   if (argc != 3)
   9   {
  10     ROS_INFO("usage: add_two_ints_client X Y");
  11     return 1;
  12   }
  13 
  14   ros::NodeHandle n;
  15   ros::ServiceClient client = n.serviceClient<rospy_tutorials::AddTwoInts>("add_two_ints");
  16   rospy_tutorials::AddTwoInts srv;
  17   srv.request.a = atoll(argv[1]);
  18   srv.request.b = atoll(argv[2]);
  19   if (client.call(srv))
  20   {
  21     ROS_INFO("Sum: %ld", (long int)srv.response.sum);
  22   }
  23   else
  24   {
  25     ROS_ERROR("Failed to call service add_two_ints");
  26     return 1;
  27   }
  28 
  29   return 0;
  30 }

程式流程: 先初始化一個node跟他的handler,然後建一個client指定要打add_two_ints那個service,接著把要相加的參數代入,然後就call service並把回傳的response底下的sum屬性的資料印出來。大概就是這樣啦!

15   ros::ServiceClient client = n.serviceClient<rospy_tutorials::AddTwoInts>("add_two_ints");

這邊就是先設定好ServiceClient要打的是add_two_ints這個service,函式定義如下:

template<class Service >
ServiceClient ros::NodeHandle::serviceClient(const std::string &service_name, bool persistent = false, const M_string &header_values = M_string())

第一個參數就是service的名稱囉! 第二個參數persistent表示是否要讓這個client一直跟server連接,這個設定可以允許client在呼叫service的時候連去別的node,但使用上需要很小心,需要自己定義連結失敗的時候要怎麼處理。
第三個參數header是在每次呼叫的時候都可以放在標頭的參數,可以用來製作cookies。(實際上跟python的client操作一模一樣,只是我怕有些人只看C++版本的所以複製貼上一遍 XD)

  16   rospy_tutorials::AddTwoInts srv;
  17   srv.request.a = atoll(argv[1]);
  18   srv.request.b = atoll(argv[2]);

這邊就是在把資料塞進去request裡面,接著

  19   if (client.call(srv))

就是call這個service啦! call的函式定義超簡單的:

template<class Service >
bool ros::ServiceClient::call(Service &service)	

就是給他service的物件就對了XD

接下來就是編譯啦,相依的模組我們在上一篇已經設定完了,所以這邊就只要在CMakeList.txt裡面加入執行檔就好囉!

add_executable(add_two_ints_client src/add_two_ints_client.cpp)
target_link_libraries(add_two_ints_client ${catkin_LIBRARIES})

編譯完後執行程式的畫面:
client執行畫面

在實作的時候我發現C++版本的service結構有點小複雜,不知道我寫起來大家有沒有辦法看得懂 QQ 我會在下一篇針對c++版本的service再說明一下。

參考資料

ROS Tutorials - service in cpp
ROS wiki - roscpp Services
ROS doc - NodeHandler(ServiceClient的建構函式定義)
ROS doc - ServiceClient class


上一篇
Day 18 - 使用C++撰寫Server Node
下一篇
Day 20 - ROS Services 常用指令 & Service Structure
系列文
ROS自學筆記30
圖片
  直播研討會
圖片
{{ item.channelVendor }} {{ item.webinarstarted }} |
{{ formatDate(item.duration) }}
直播中

尚未有邦友留言

立即登入留言